﻿using System;

using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;
using System.Web;

namespace WebCore.Helpers
{
    /// <summary>
    /// Image resize referece
    /// http://www.switchonthecode.com/tutorials/csharp-tutorial-image-editing-saving-cropping-and-resizing
    /// http://stackoverflow.com/questions/1931290/c-why-resize-image-will-increase-the-file-size
    /// http://www.codeproject.com/KB/GDI-plus/imageresize.aspx
    /// http://www.c-sharpcorner.com/UploadFile/raj1979/ImageThumbnail11062008011338AM/ImageThumbnail.aspx
    /// http://www.csharp-station.com/Articles/Thumbnails.aspx
    /// http://stackoverflow.com/questions/419584/what-is-the-difference-between-jpg-jpeg-png-bmp-gif-tiff-im
    /// 
    /// 
    /// </summary>
    public class ImageHelper
    {

        public int ImageWidth { get; set; }
        public int ImageHight { get; set; }


        #region image method

        public static ImageHelper GetImageInfo(string imageFilePath)
        {
            var info = new ImageHelper();
            using (Image img = Image.FromFile(imageFilePath))
            {
                info.ImageHight = img.Height;
                info.ImageWidth = img.Width;
            }

            return info;
        }

        public static void ResizeImage(string originalFilename, string resizeFilename, int imageWidth, bool IsCropping)
        {
            //pass in value for the width
            using (Image imgOriginal = Image.FromFile(originalFilename))
            {
                // if less than what we want it, leave it like original size
                if (imgOriginal.Width < imageWidth && !IsCropping)
                    imageWidth = imgOriginal.Width;

                var imgActual = ResizeImage(imgOriginal, imageWidth);

                SaveCompressed(imgActual, resizeFilename, ".jpg", 75L);

            }
        }

    

        public static string CropImage(int X, int Y, int w, int h, string originalFile, string newImagePath, long quality)
        {
            using (Image img = Image.FromFile(originalFile))
            {
                using (System.Drawing.Bitmap _bitmap = new System.Drawing.Bitmap(w, h))
                {
                    _bitmap.SetResolution(img.HorizontalResolution, img.VerticalResolution);
                    using (Graphics _graphic = Graphics.FromImage(_bitmap))
                    {
                        string extension = Path.GetExtension(originalFile);
                        string croppedFileName = Guid.NewGuid().ToString();
                        string path = newImagePath; ;

                        _graphic.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
                        _graphic.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
                        _graphic.PixelOffsetMode = System.Drawing.Drawing2D.PixelOffsetMode.HighQuality;
                        _graphic.CompositingQuality = System.Drawing.Drawing2D.CompositingQuality.HighQuality;
                        _graphic.DrawImage(img, 0, 0, w, h);
                        _graphic.DrawImage(img, new Rectangle(0, 0, w, h), X, Y, w, h, GraphicsUnit.Pixel);

                       
                        string newFullPathName = string.Concat(path, croppedFileName, extension);

                        SaveCompressed(_bitmap, newFullPathName, extension, quality);

                        return croppedFileName + extension;
                    }
                }
            }
        }

        /// <summary>
        /// reduce the size of image
        /// http://stackoverflow.com/questions/684092/create-thumbnail-and-reduce-image-size
        /// 
        /// </summary>
        /// <param name="img"></param>
        /// <param name="filePath"></param>
        /// <param name="extension"></param>
        /// <param name="quality"></param>
        private static void SaveCompressed(Bitmap _bitImg, string filePath, string extension, long quality)
        {
            using (EncoderParameters encoderParameters = new EncoderParameters(1))
            {
                encoderParameters.Param[0] = new EncoderParameter(Encoder.Quality, quality);
                _bitImg.Save(filePath, GetImageCodec(extension), encoderParameters);
            }
        }

        // Find the right codec
        private static ImageCodecInfo GetImageCodec(string extension)
        {
            extension = extension.ToUpperInvariant();
            ImageCodecInfo[] codecs = ImageCodecInfo.GetImageEncoders();
            foreach (ImageCodecInfo codec in codecs)
            {
                if (codec.FilenameExtension.Contains(extension))
                {
                    return codec;
                }
            }
            return codecs[1];
        }


        /// <summary>
        /// Proportionally resizes a Size structure.
        /// This function will proportionally resize a Size structure. 
        /// Just provide it the maximum height/width and it will return a size that fits within that rectangle.
        /// </summary>
        /// <param name="sz"></param>
        /// <param name="maxWidth"></param>
        /// <param name="maxHeight"></param>
        /// <returns></returns>
        public static Size Resize(Size sz, int maxWidth, int maxHeight)
        {
            int height = sz.Height;
            int width = sz.Width;

            double actualRatio = (double)width / (double)height;
            double maxRatio = (double)maxWidth / (double)maxHeight;
            double resizeRatio;

            if (actualRatio > maxRatio)
                // width is the determinate side.
                resizeRatio = (double)maxWidth / (double)width;
            else
                // height is the determinate side.
                resizeRatio = (double)maxHeight / (double)height;

            width = (int)(width * resizeRatio);
            height = (int)(height * resizeRatio);

            return new Size(width, height);
        }

        public static Bitmap ResizeImage(Image img, int newWidth, int newHeight)
        {
            var newImg = new Bitmap(newWidth, newHeight, PixelFormat.Format24bppRgb);

            using (Graphics g = Graphics.FromImage(newImg))
            {
                g.InterpolationMode = InterpolationMode.HighQualityBicubic;
                g.SmoothingMode = SmoothingMode.HighQuality;
                g.CompositingQuality = CompositingQuality.HighQuality;

                g.DrawImage(img, 0, 0, newWidth, newHeight);
            }

            return newImg;
        }

        public static Bitmap ResizeImage(Image img, int newWidth)
        {
            // get the image height
            int newHeight = Convert.ToInt32(Math.Round(Convert.ToDouble(
               ((double)newWidth / (double)img.Width * (double)img.Height))));

            var newImg = new Bitmap(newWidth, newHeight, PixelFormat.Format24bppRgb);
            using (Graphics g = Graphics.FromImage(newImg))
            {
                g.InterpolationMode = InterpolationMode.HighQualityBicubic;
                g.SmoothingMode = SmoothingMode.HighQuality;
                g.CompositingQuality = CompositingQuality.HighQuality;

                g.DrawImage(img, 0, 0, newWidth, newHeight);
            }

            return newImg;
        }


        #endregion


    }
}
